
package codeGenerate.custom.generater;

import java.io.*;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import codeGenerate.common.freemarker.CommonFunction;
import codeGenerate.common.utils.SystemUtils;
import codeGenerate.custom.converter.CustomConverter;
import codeGenerate.custom.tempalte.TemPathCustomAbstract;
import codeGenerate.custom.vo.CustomConfigVo;
import codeGenerate.custom.vo.CustomPropertyVo;
import freemarker.template.Configuration;
import freemarker.template.DefaultObjectWrapper;
import freemarker.template.Template;
import freemarker.template.TemplateException;

/**
 * 自定义代码生成器
 * @author fudewei
 */
public class CustomGenerater {

	private CustomConfigVo configVo;

	public void generateCode() throws IOException, TemplateException, ClassNotFoundException, InstantiationException, IllegalAccessException {
		System.out.println(">>>>>>>>>>>>>>>>>>>[" + configVo.getBeanDescription() + "]生成开始<<<<<<<<<<<<<<<<<<<");
		System.out.println(configVo);

		Map<String, Object> root = new HashMap<String, Object>();
		//定义模板常量
		List<CustomPropertyVo> requestColumnList = convert(configVo.getRequest());
		SystemUtils.logIterate("request", requestColumnList);
		List<CustomPropertyVo> responseColumnList = convert(configVo.getResponse());
		SystemUtils.logIterate("response", responseColumnList);
		root.put("requestColumnList", requestColumnList);
		root.put("responseColumnList", responseColumnList);
		root.put("config", configVo);
		root.put("commonFunction", new CommonFunction());
		Configuration cfg = new Configuration();
		cfg.setClassicCompatible(true);
		cfg.setDirectoryForTemplateLoading(new File(configVo.getTemplateDirectory()));
		cfg.setObjectWrapper(new DefaultObjectWrapper());
		//根据模版路径生成相应的代码
		Class<?> tempateClass = Class.forName(configVo.getTemplate());
		TemPathCustomAbstract temPathAbstract = (TemPathCustomAbstract) tempateClass.newInstance();
		Map<String, String> tplFileMap = temPathAbstract.getPathMap(configVo);
		for (Map.Entry<String, String> entry : tplFileMap.entrySet()) {
			String tempalteFile = entry.getKey();
			String generateFile = entry.getValue();
			Template temp = cfg.getTemplate(tempalteFile);
			File file = new File(generateFile);
			if (!file.exists()) {
				file.getParentFile().mkdirs();
				file.createNewFile();
			}
			OutputStream writer = new FileOutputStream(new File(generateFile));
			Writer out = new OutputStreamWriter(writer);
			temp.process(root, out);
			writer.flush();
			writer.close();
			System.out.println("模板:" + tempalteFile + "==>>生成文件==>>" + generateFile);
		}

		System.out.println(">>>>>>>>>>>>>>>>>>>表名[" + configVo.getBeanDescription() + "]生成结束<<<<<<<<<<<<<<<<<<<");
		System.out.println("\n");
	}

	private List<CustomPropertyVo> convert(String fieldStr) {
		try {
			Class<?> converterClass = Class.forName(configVo.getConverter());
			CustomConverter converter = (CustomConverter) converterClass.newInstance();
			return converter.convert(fieldStr);
		} catch (Exception e) {
			throw new RuntimeException(e);
		}
	}

	public CustomConfigVo getConfigVo() {
		return configVo;
	}

	public void setConfigVo(CustomConfigVo configVo) {
		this.configVo = configVo;
	}
}
